#include "sqlite_helper.h"

SqliteHelper::SqliteHelper(const QString& dbPath, QObject* parent)
    : QObject(parent), m_dbPath(dbPath)
{
}

SqliteHelper::~SqliteHelper()
{
    close();
}

QSqlDatabase SqliteHelper::getDatabase()
{
    QString connName = QString("sqlite_conn_%1").arg((quintptr)QThread::currentThreadId());
    if (!QSqlDatabase::contains(connName)) {
        QSqlDatabase db = QSqlDatabase::addDatabase("QSQLITE", connName);
        db.setDatabaseName(m_dbPath);
        db.open();
    }
    return QSqlDatabase::database(connName);
}

bool SqliteHelper::open()
{
    QMutexLocker locker(&m_mutex);
    QSqlDatabase db = getDatabase();
    if (!db.isOpen()) {
        if (!db.open()) {
            qWarning() << "Open DB failed:" << db.lastError().text();
            return false;
        }
    }
    return true;
}

void SqliteHelper::close()
{
    QMutexLocker locker(&m_mutex);
    QString connName = QString("sqlite_conn_%1").arg((quintptr)QThread::currentThreadId());
    if (QSqlDatabase::contains(connName)) {
        QSqlDatabase db = QSqlDatabase::database(connName);
        if (db.isOpen()) db.close();
        QSqlDatabase::removeDatabase(connName);
    }
}

bool SqliteHelper::createTable(const QString& sql)
{
    QMutexLocker locker(&m_mutex);
    QSqlQuery query(getDatabase());
    if (!query.exec(sql)) {
        qWarning() << "Create table failed:" << query.lastError().text();
        return false;
    }
    return true;
}

bool SqliteHelper::execSql(const QString& sql, const QVariantList& args)
{
    QMutexLocker locker(&m_mutex);
    QSqlQuery query(getDatabase());
    query.prepare(sql);
    for (int i = 0; i < args.size(); ++i) {
        query.addBindValue(args[i]);
    }
    if (!query.exec()) {
        qWarning() << "Exec SQL failed:" << query.lastError().text();
        return false;
    }
    return true;
}

QSqlQuery SqliteHelper::query(const QString& sql, const QVariantList& args)
{
    QMutexLocker locker(&m_mutex);
    QSqlQuery query(getDatabase());
    query.prepare(sql);
    for (int i = 0; i < args.size(); ++i) {
        query.addBindValue(args[i]);
    }
    if (!query.exec()) {
        qWarning() << "Query failed:" << query.lastError().text();
    }
    return query;
}

bool SqliteHelper::deleteData(const QString& table, const QString& condition)
{
    QMutexLocker locker(&m_mutex);
    QString sql = QString("DELETE FROM %1 WHERE %2").arg(table, condition);
    QSqlQuery query(getDatabase());
    if (!query.exec(sql)) {
        qWarning() << "Delete failed:" << query.lastError().text();
        return false;
    }
    return true;
}

bool SqliteHelper::updateData(const QString& table, const QString& setClause, const QString& condition)
{
    QMutexLocker locker(&m_mutex);
    QString sql = QString("UPDATE %1 SET %2 WHERE %3").arg(table, setClause, condition);
    QSqlQuery query(getDatabase());
    if (!query.exec(sql)) {
        qWarning() << "Update failed:" << query.lastError().text();
        return false;
    }
    return true;
}
